import os
import json
from typing import Optional, Dict, Any

class FileOperations:
    """文件操作工具类"""
    
    @staticmethod
    def read_file(file_path: str) -> str:
        """
        读取文件内容
        
        Args:
            file_path: 文件路径
            
        Returns:
            文件内容字符串
            
        Raises:
            FileNotFoundError: 文件不存在
            PermissionError: 没有读取权限
        """
        if not os.path.exists(file_path):
            raise FileNotFoundError(f"文件不存在: {file_path}")
        
        if not os.access(file_path, os.R_OK):
            raise PermissionError(f"没有读取权限: {file_path}")
        
        try:
            with open(file_path, 'r', encoding='utf-8') as file:
                return file.read()
        except UnicodeDecodeError:
            # 如果UTF-8解码失败，尝试其他编码
            with open(file_path, 'r', encoding='gbk') as file:
                return file.read()
    
    @staticmethod
    def write_file(file_path: str, content: str) -> None:
        """
        写入文件内容
        
        Args:
            file_path: 文件路径
            content: 要写入的内容
        """
        # 确保目录存在
        os.makedirs(os.path.dirname(file_path), exist_ok=True)
        
        with open(file_path, 'w', encoding='utf-8') as file:
            file.write(content)
    
    @staticmethod
    def get_file_info(file_path: str) -> Dict[str, Any]:
        """
        获取文件信息
        
        Args:
            file_path: 文件路径
            
        Returns:
            包含文件信息的字典
        """
        if not os.path.exists(file_path):
            raise FileNotFoundError(f"文件不存在: {file_path}")
        
        stat = os.stat(file_path)
        return {
            "name": os.path.basename(file_path),
            "path": os.path.abspath(file_path),
            "size": stat.st_size,
            "created": stat.st_ctime,
            "modified": stat.st_mtime,
            "is_file": os.path.isfile(file_path),
            "is_dir": os.path.isdir(file_path)
        }
    
    @staticmethod
    def list_directory(directory: str = ".") -> list:
        """
        列出目录内容
        
        Args:
            directory: 目录路径，默认为当前目录
            
        Returns:
            目录内容列表，包含文件和文件夹信息
        """
        if not os.path.exists(directory):
            raise FileNotFoundError(f"目录不存在: {directory}")
        
        if not os.path.isdir(directory):
            raise NotADirectoryError(f"不是目录: {directory}")
        
        items = []
        for item in os.listdir(directory):
            item_path = os.path.join(directory, item)
            item_info = FileOperations.get_file_info(item_path)
            items.append(item_info)
        
        return items
    
    @staticmethod
    def analyze_file_content(content: str, max_lines: int = 50) -> Dict[str, Any]:
        """
        分析文件内容
        
        Args:
            content: 文件内容
            max_lines: 最大分析行数
            
        Returns:
            文件分析结果
        """
        lines = content.split('\n')
        total_lines = len(lines)
        
        # 获取文件开头部分
        preview_lines = lines[:min(max_lines, total_lines)]
        preview = '\n'.join(preview_lines)
        
        # 简单的内容类型检测
        content_type = "文本"
        if any(keyword in content.lower() for keyword in ['import', 'def ', 'class ', 'function ', 'print(', 'return ']):
            content_type = "Python代码"
        elif any(keyword in content.lower() for keyword in ['<html', '<body', '<div', '<head']):
            content_type = "HTML"
        elif any(keyword in content.lower() for keyword in ['{', '}', '":', '[', ']']):
            try:
                json.loads(content)
                content_type = "JSON"
            except:
                content_type = "文本"
        elif any(keyword in content.lower() for keyword in ['#include', 'int main', 'void ', 'printf']):
            content_type = "C/C++代码"
        elif any(keyword in content.lower() for keyword in ['package ', 'import ', 'public class']):
            content_type = "Java代码"
        
        return {
            "total_lines": total_lines,
            "total_chars": len(content),
            "content_type": content_type,
            "preview": preview,
            "has_more": total_lines > max_lines
        }
